#include "ExplosionParticleSystem.h"
#include "iRenderer.h"
#include <cmath>
#include <vector>

using namespace neiderra::rendering;

//float radius=2.0f;
//
//float angle=90*3.14/180;
//double t_passed = 0.0, t_accum = 0.0, t;
//double Pt = 150;
//float size=0.2f, dsize=0.012f;
const float static_grow=0.001f;
//float v0 = 5.0f, v1, oldv=v0;
//float v=0, a=-0.005f, s, s1, s0=0;
//unsigned n=0;
//float olds;
//bool stop_emitter = false;
	
typedef std::vector<ExplosionArrowParticleSystem*> Arrows;
Arrows arrows;

int ExplosionArrowParticleSystem::update(double deltaT)
{
	t_passed += deltaT;
	t_accum += deltaT*0.001;

	if(n<getMaxParticles() && t_passed >= Pt){
		PolyParticle* pp = (PolyParticle*)this->add();
		pp->texture = _texture;
		pp->size = size;
		const float tmptime = this->getMaxLifetime();
		pp->lifetime = tmptime;

		size += dsize;
		n++;
		t_passed = 0.0;
		if(n==this->getMaxParticles()) {
			stop_emitter = true;
		}
	}

	const float deltat = 0.001*deltaT;
	v1=v0+a*deltat;
	s1 = s0+v1*deltat;
	if(abs(s1-s0) <= 0.001){
		a=0;v0=0;
	}
	float ds = s1-s0;

	s0=s1;
	v0=v1;
	

	for(Particles::iterator i = _particles.begin();
		i != _particles.end();
		i++)
	{
		PolyParticle* pp = (PolyParticle*)*i;
		pp->size += static_grow;
		pp->lifetime -= deltaT;
		
		pp->pos.x += std::cos(angle)*ds;
		pp->pos.z += std::sin(angle)*ds;

		if(stop_emitter) {
			continue;
		}

		pp->pos.y += (2-pp->pos.y)*deltat;
	}

	return 0;
}

void ExplosionArrowParticleSystem::reset()
{
	_particles.clear();
}

void ExplosionArrowParticleSystem::setup(float angle_, float r_, float v0_, float Pt_)
{
	s0=0;

	Pt = Pt_;
	angle = angle_;
	radius = r_;
	v0=v0_;
	n=0;

	t_passed = 0.0, t_accum = 0.0, t;
	size=0.2f, dsize=0.012f;
	stop_emitter = false;
}

void ExplosionArrowParticleSystem::initParticles()
{
	t = (getMaxParticles()+1)*Pt*0.001;
	s = radius;
	a = 2*(s-v0*t)/(t*t);
}

void ExplosionParticleSystem::initParticles()
{
	ExplosionArrowParticleSystem* aps1 = new ExplosionArrowParticleSystem();
	aps1->setMaxLifetime(7000);
	aps1->setMaxParticles(15);
	aps1->setup(0.0f, 2.0f, 3.0f, 100);
	aps1->initParticles();

	ExplosionArrowParticleSystem* aps2 = new ExplosionArrowParticleSystem();
	aps2->setMaxLifetime(7000);
	aps2->setMaxParticles(15);
	aps2->setup(1.45f, 2.0f, 3.0f, 100);
	aps2->initParticles();

	ExplosionArrowParticleSystem* aps3 = new ExplosionArrowParticleSystem();
	aps3->setMaxLifetime(7000);
	aps3->setMaxParticles(15);
	aps3->setup(4.45f, 2.0f, 3.0f, 100);
	aps3->initParticles();

	arrows.push_back(aps1);
	arrows.push_back(aps2);
	arrows.push_back(aps3);
}


int ExplosionParticleSystem::update(double deltaT)
{
	Arrows::iterator i = arrows.begin();
	for(;i!=arrows.end();i++)
	{
		ExplosionArrowParticleSystem* aps = (*i);
		aps->update(deltaT);
	}
	return 0;
}

void ExplosionParticleSystem::render(iRenderer* r)
{
	Arrows::iterator i = arrows.begin();
	for(;i!=arrows.end();i++)
	{
		ExplosionArrowParticleSystem* aps = (*i);
		aps->render(r);
	}
}

void ExplosionParticleSystem::reset()
{
	//Arrows::iterator i = arrows.begin();
	//for(;i!=arrows.end();i++)
	//{
	//	ExplosionArrowParticleSystem* aps = (*i);
	//	aps->reset();
	//}
	arrows.clear();
}
